package com.zzyl.nursing.service.impl;

import cn.hutool.core.util.ObjectUtil;
import cn.hutool.core.util.StrUtil;
import cn.hutool.http.HttpRequest;
import cn.hutool.http.HttpUtil;
import cn.hutool.json.JSONObject;
import cn.hutool.json.JSONUtil;
import com.zzyl.common.exception.ServiceException;
import com.zzyl.nursing.service.WechatService;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.stereotype.Service;

import java.util.Collections;
import java.util.HashMap;
import java.util.Map;

@Service
@Slf4j
public class WechatServiceImpl implements WechatService {
    private static final String GET_OPENID_URL = "https://api.weixin.qq.com/sns/jscode2session";

    private static final String ACCESS_ID_URL = "https://api.weixin.qq.com/cgi-bin/token";

    private static final String GET_PHONE_URL = "https://api.weixin.qq.com/wxa/business/getuserphonenumber?access_token={}";

    @Value("${wechat.appid}")
    private String appid;
    @Value("${wechat.appSecret}")
    private String secret;

    /*获取openId*/
    public String getOpenid(String code) {
        //GET https://api.weixin.qq.com/sns/jscode2session
        String url = GET_OPENID_URL;
        String result = HttpRequest.get(url)
                .form("appid", appid)
                .form("secret", secret)
                .form("js_code", code)
                .form("grant_type", "authorization_code")
                .timeout(5000)
                .execute()
                .body();
        JSONObject entries = JSONUtil.parseObj(result);
        String openId = entries.getStr("openid");
        log.info("获取openId结果{} = ", openId);
        if (StrUtil.isEmpty(openId)) {
            throw new ServiceException("获取openId失败,请稍后重试");
        }
        return openId;
    }

    /*获取微信授权，有效期为两小时
     * 优化：放在redis里设置有效期为一小时50分钟
     * 获取时优先从redis中取*/
    private String getAccessToken() {
        String body = HttpRequest.get(ACCESS_ID_URL)
                //get请求中的form参数是普通参数
                .form("appid", appid)
                .form("secret", secret)
                //文档里要求grant_type是client_credential
                .form("grant_type", "client_credential")
                .timeout(5000)
                .execute()
                .body();
        JSONObject jsonObject = JSONUtil.parseObj(body);
        System.out.println("jsonObject = " + jsonObject);
        String accessToken = jsonObject.getStr("access_token");
        if (StrUtil.isEmpty(accessToken)) {
            throw new ServiceException("获取access_token失败,请稍后重试");
        }
        return accessToken;

    }

    /*获取手机号*/
    public String getPhone(String phoneCode) {
        String url = GET_PHONE_URL;
        url = StrUtil.format(url, getAccessToken());
        System.out.println("url = " + url);
        //构建一个map仅能放下一个keyvalue
        Map<String, String> map = Collections.singletonMap("code", phoneCode);
        String result = HttpRequest.post(url)
                .body(JSONUtil.toJsonStr(map))
                .timeout(5000)
                .execute()
                .body();
        JSONObject jsonObject = JSONUtil.parseObj(result);

        String byPath = jsonObject.getByPath("phone_info.purePhoneNumber", String.class);
        if (StrUtil.isEmpty(byPath)) {
            throw new ServiceException("获取手机号失败,请稍后重试");
        }
        return byPath;
    }
}